import type TiledMap from "tiled-types";
import type { Direction } from "@/config/characterConfig";

import House from "@/assets/images/building/house.png";
import BaseTiles from "@/assets/images/tiles/baseTiles.png";
import FarmHouse from "@/assets/images/tiles/farmhouse_tiles.png";

import { drawGrid, loadImage } from ".";
import { updateCamera } from "./camera";
import { Hats } from "@/config/clothing";
import { globalScale } from "@/config/static";
import { useTimeStore } from "@/store/timeStore";
import { useUserStore } from "@/store/userStore";
import { processLayers } from "./layerProcessor";
import { treeManager } from "@/utils/treeManager";
import { TreeGrowthStage } from "@/config/treeConfig";
import { handlePlayerMovement } from "./playerController";
import { SceneType, useSceneStore } from "@/store/sceneStore";
import { extractCollisionAreas, renderCollisionAreas } from "./collision";

/**
 * 加载地图
 * @param mapPath 地图路径，以 /src 开头
 * @returns 地图数据
 */
export const loadMap = async (mapPath: string): Promise<TiledMap> => {
  try {
    if (!mapPath) {
      return Promise.reject("地图路径不能为空");
    }
    if (!mapPath.startsWith("/src")) {
      return Promise.reject("地图路径必须以 /src 开头");
    }
    const response = await fetch(mapPath);
    const mapData = await response.json();

    extractCollisionAreas(mapData);

    return mapData as TiledMap;
  } catch (error) {
    console.error("加载地图失败：", error);
    throw error;
  }
};

let lastTime = performance.now();
let animationId: number | null = null;
/**
 * 渲染地图主函数
 * @param ctx 画布上下文
 * @param map 地图数据
 * @param scale 缩放比例
 */
export const renderMap = async (
  ctx: CanvasRenderingContext2D,
  map: TiledMap,
  scale: number = globalScale
) => {
  if (animationId !== null) {
    cancelAnimationFrame(animationId);
    animationId = null;
  }

  const houseTileset = await loadImage(House);
  const baseTileset = await loadImage(BaseTiles);
  const farmHouseTileset = await loadImage(FarmHouse);

  const tileset: Record<string, HTMLImageElement> = {
    default: baseTileset,
    house: houseTileset,
    farmhouse: farmHouseTileset,
  };

  const timeStore = useTimeStore();
  const sceneStore = useSceneStore();
  const currentScene = sceneStore.currentScene;
  const { playerPosition, playerInstance, characterSize } = useUserStore();

  // 游戏循环函数
  const animate = (timestamp: number = 0) => {
    const currentTime = performance.now();
    const deltaTime = (currentTime - lastTime) / 1000;
    lastTime = currentTime;

    // 清除画布
    ctx.clearRect(0, 0, ctx.canvas.width, ctx.canvas.height);

    // 当过渡动画正在执行时，渲染加载背景色
    if (sceneStore.transition.active) {
      ctx.save();
      ctx.fillStyle = "black";
      ctx.fillRect(0, 0, ctx.canvas.width, ctx.canvas.height);
      ctx.restore();

      // 在过渡期间不渲染任何游戏内容
      animationId = requestAnimationFrame(animate);
      return;
    }
    // 正常游戏渲染逻辑
    else {
      // 处理玩家移动
      handlePlayerMovement(timestamp);
      ctx.save();

      // 设置图像平滑属性为false，使得像素边界更加清晰，减少间隙
      ctx.imageSmoothingEnabled = false;
      ctx.scale(scale, scale);

      // 更新相机
      updateCamera(ctx);

      // 处理下层图层
      processLayers(ctx, map.layers, map, tileset, false, currentScene);

      drawGrid(ctx, map, scale);

      if (playerInstance) {
        if (sceneStore.currentScene === SceneType.FARM) {
          // 更新树木状态
          treeManager.updateTrees(deltaTime);
        }
      }

      // 根据y组表来决定渲染顺序
      if (playerInstance) {
        const playerY = playerPosition.y;
        const trees = treeManager.getAllTrees();

        treeManager.renderAllTreeShadows(ctx);

        // 先渲染Y坐标小于角色的树木（在角色后面的树）
        trees.forEach((tree) => {
          const config = treeManager.getTreeConfig(tree);

          let treeBottomY = tree.y;
          if (tree.stage === TreeGrowthStage.MATURE && config?.parts) {
            // 成熟树木，使用树干底部
            if (config.parts.trunk) {
              treeBottomY = tree.y + config.parts.trunk.height;
            }
          } else if (config && config.height) {
            treeBottomY = tree.y + config?.height;
          } else {
            treeBottomY = tree.y;
          }
          if (tree.visible) {
            treeManager.renderSingleTree(ctx, tree);
          }
        });

        // 渲染角色
        const hatsDirection =
          Hats.cowboyHat[playerPosition.direction.value as Direction];
        hatsDirection && playerInstance.setHatConfig(hatsDirection);
        playerInstance.update(playerPosition.x, playerPosition.y, 1, deltaTime);

        if (currentScene === SceneType.FARM) {
          // 再渲染Y坐标大于等于角色的树木（在角色前面的树）
          trees.forEach((tree) => {
            const config = treeManager.getTreeConfig(tree);
            if (!config) return;

            let treeBottomY = tree.y;

            if (tree.stage === TreeGrowthStage.MATURE && config.parts) {
              // 成熟树木，使用树干底部
              if (config.parts.trunk) {
                treeBottomY = tree.y;
              } else if (config.height) {
                treeBottomY = tree.y + config.height;
              } else {
                treeBottomY = tree.y;
              }
            }

            if (
              treeBottomY >= playerY + characterSize.height &&
              tree.stage !== TreeGrowthStage.STUMP
            ) {
              if (tree.visible) {
                treeManager.renderSingleTree(ctx, tree);
              }
            }
          });
        }
      } else if (currentScene === SceneType.FARM) {
        // 如果没有角色实例，直接渲染所有树木（只在农场场景）
        const trees = treeManager.getAllTrees();
        trees.forEach((tree) => {
          if (tree.visible) {
            treeManager.renderSingleTree(ctx, tree);
          }
        });
      }

      if (playerInstance) {
        treeManager.updateTreeTransparency(
          playerPosition.x,
          playerPosition.y,
          characterSize.width,
          characterSize.height
        );
      }

      // 渲染碰撞区域
      renderCollisionAreas(ctx, 1);

      // 只在农场场景处理上层图像
      if (currentScene === SceneType.FARM) {
        // 处理上层图像
        processLayers(ctx, map.layers, map, tileset, true, currentScene);
      }

      if (currentScene === SceneType.FARM) {
        // 天黑遮罩
        const darkness = 1 - timeStore.brightnessFactor;
        ctx.fillStyle = `rgba(0, 0, 0, ${darkness * 0.8})`;
        ctx.fillRect(
          -ctx.canvas.width / 2,
          -ctx.canvas.height / 2,
          ctx.canvas.width * 4,
          ctx.canvas.height * 4
        );
      }

      ctx.restore();
    }

    // 继续下一帧动画
    animationId = requestAnimationFrame(animate);
  };

  // 开始动画循环
  animationId = requestAnimationFrame(animate);
};
